package com.etone.smartAudit.service;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.RandomUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.etone.smartAudit.domain.PPushLog;
import com.etone.smartAudit.domain.PTodo;
import com.etone.smartAudit.dto.PortalPushDTO;
import com.etone.smartAudit.error.CustomParameterizedException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/***
 * portal推送服务
 */
@Slf4j
@Service
public class PortalPushService {
//    public final static String PUSH_URL = "http://eiptodotest.gmcc.net/appsync_test/servlet";
//    public final static String APPNAME = "广东大数据智慧审计中台"; //portal分配的应用名
//    public final static String userid = "xtsgssmartaudit";
//    public final static String password = "Abc@#123";

    @Value("${portal.url:http://eiptodotest.gmcc.net/appsync_test/servlet}")
    private String url;
    @Autowired
    private RestTemplateRequest request;

    @Value("${portal.appName:广东大数据智慧审计中台}")
    private String appName;
    //
    @Lazy
    @Autowired
    private PPushLogService pPushLogService;
    /***
     * 系统推送id
     */
    @Value("${portal.sysId:GMCCSMARTAUDIT_ACCESSRIGHT}")
    private String sysId;

    @Value("${portal.password:Abc@#123}")
    private String password;

    @Value("${portal.userid:xtsgssmartaudit}")
    private String userid;

    @Autowired
    private PTodoService pTodoService;

    /**
     * 执行代办推送
     *
     * @param pushLog
     * @throws Exception
     */
    public void push(PPushLog pushLog) throws Exception {
        //设置推送参数
        PortalPushDTO portalPushDTO = new PortalPushDTO();
        JSONObject param = JSON.parseObject(pushLog.getMsg());
        portalPushDTO.setSeqno(pushLog.getSeqno());
        portalPushDTO.setTodoId(param.getString("todoId"));
        portalPushDTO.setTodoTitle(param.getString("todoTitle"));
        portalPushDTO.setUrl(param.getString("url"));
        portalPushDTO.setType(param.getString("type"));
        portalPushDTO.setBusiness(pushLog.getBusiness());
        portalPushDTO.setOwner(param.getString("owner"));
        portalPushDTO.setParentOwner(param.getString("parentOwner"));
        portalPushDTO.setPushLogId(pushLog.getId());
        realPush(portalPushDTO, pushLog);
    }

    /***
     * 执行代办推送
     * @param portalPushDTO
     * @throws Exception
     */
    @Transactional(rollbackFor = Exception.class)
    public void push(PortalPushDTO portalPushDTO) throws Exception {
        Integer logId = portalPushDTO.getPushLogId();
        if (logId != null) {
            //获取请求参数
            PPushLog pushLog = pPushLogService.getById(logId);
            if (pushLog == null) {
                log.error("==========代办日志不存在=======");
                throw new Exception("代办日志不存在");
            }
            push(pushLog);
        } else {
            portalPushDTO.setSeqno(RandomUtil.randomString(32));
            //添加一条代办记录
            PTodo ptodo = pTodoService.createPTodoService(portalPushDTO);
            portalPushDTO.setTodoId(String.valueOf(ptodo.getTodoId()));
            realPush(portalPushDTO, null);
        }
    }

    /***
     * 执行代办推送
     * @param portalPushDTO
     * @param pushLog
     * @throws Exception
     */
    private void realPush(PortalPushDTO portalPushDTO, PPushLog pushLog) throws Exception {

        Map<String, String> head = new HashMap<>();
        /**
         * business=done&seqno=1&timestamp=20211208152519160&appname=GMCCSMARTAUDIT_ACCESSRIGHT
         * 名称	必选	类型	长度	说明
         * seqno	是	string		唯一流水号，只在log4j日志中记录，排查使用
         * appname	是	string		应用名称，如:OA。如果portal侧禁用该应用，那么应用的所有消息都会被拒绝。
         * business	是	string		业务名称，如:todo,done,toread,read
         * uid	是	string		Portal分配用户名
         * password	是	string		Portal分配密码
         * timestamp	是	string		时间戳，格式yyyyMMddHHmmssSSS
         */
        head.put("seqno", portalPushDTO.getSeqno());
        head.put("appname", sysId);
        head.put("business", portalPushDTO.getBusiness());
        head.put("uid", userid);
        head.put("password", password);
//        head.put("Content-type", "application/json:charset=UTF-8");
        head.put("timestamp", DateUtil.format(new Date(), "yyyyMMddHHmmssSSS"));
        JSONObject param = new JSONObject();
        /***
         *        "todoId":"123",
         *         "appName":"财务集中报账",
         *         "owner":"dwzhouzongbing",
         *         "parentOwner":"刘滨锐：同意",
         *         "todoTitle":"付罗国珍办市场部报销2017年2月用车经营费用",
         *         "url":"http://ip:port/p/s?id=123",
         *         "createTime":"2017-03-06 13:06:33",
         *         "modifyTime":"2017-03-06 13:06:33",
         *         "type":"A"
         */
        param.put("todoId", portalPushDTO.getTodoId());
        param.put("appName", sysId);
        param.put("owner", portalPushDTO.getOwner());
        param.put("parentOwner", portalPushDTO.getParentOwner());
        param.put("todoTitle", portalPushDTO.getTodoTitle());
        param.put("url", portalPushDTO.getUrl());
        param.put("createTime", DateUtil.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
        param.put("modifyTime", DateUtil.format(new Date(), "yyyy-MM-dd HH:mm:ss"));
        param.put("type", portalPushDTO.getType());
        String realUrl = String.format("%s?seqno=1&appname=%s&business=%s&timestamp=%s",
                url, sysId, portalPushDTO.getBusiness(), head.get("timestamp"));

        log.error("请求头为:", JSON.toJSONString(head));
        log.error("参数为:", JSON.toJSONString(param));
        //添加到日志文件
        PPushLog log = pPushLogService.add(portalPushDTO, param.toJSONString());
        /***
         * 000	成功
         * 901~920	http head参数验证不通过
         * 921~940	处理失败
         * 999	未知异常
         */
        JSONArray array = new JSONArray();
        array.add(param);
        request.postRequestBody(array, realUrl, head, result -> {
            //处理成功，则更新为成功
            JSONObject data = JSON.parseObject(result);
            String code = data.getString("code");
            if ("000".equals(code)) {
                //更新为成功状态
                pPushLogService.success(log);
            } else {
                throw new CustomParameterizedException(data.getString("message"));
            }
        });
    }

}
